#include <stdio.h>

char *trans(char *a, int n, int i)
{
    int count = 0, s = 0, t;
    char c;

    while (count < n) {
        t = s;
        c = a[t];
        while ((t+i)%n != s) {
            a[t] = a[(t+i)%n];
            t = (t+i)%n;
            count ++;
        }
        a[t] = c;
        count ++;
        s ++;
    }

    return a;
}

char *trans_2(char *a, int n, int i)
{
    int t, j;

    if (i == 0 || i == n)
        return a;

    if (i == 1) {
        t = a[0];
        while (i < n) {
            a[i-1] = a[i-1] ^ a[i];
            a[i] = a[i-1] ^ a[i];
            a[i-1] = a[i-1] ^ a[i];
            i ++;
        }
        a[i-1] = t;
        return a;
    }

    if (i <= n-i) {
        for (j = 0; j < i; j++) {
            a[j] = a[j] ^ a[n-i+j];
            a[n-i+j] = a[j] ^ a[n-i+j];
            a[j] = a[j] ^ a[n-i+j];
        }
        return trans_2(a, n-i, i); 
    }
    else {
        for (j = 2*i-n; j < i; j++) {
            a[j] = a[j] ^ a[n-i+j];
            a[n-i+j] = a[j] ^ a[n-i+j];
            a[j] = a[j] ^ a[n-i+j];
        }
        return trans_2(a, i, 2*i-n); 
    }
}

void reverse(char *a, int i, int j)
{
    while (i < j) {
        a[i] = a[i] ^ a[j];
        a[j] = a[i] ^ a[j];
        a[i] = a[i] ^ a[j];
        i ++;
        j --;
    }
}

char *trans_3(char *a, int n, int i)
{
    reverse(a, 0, i-1);
    reverse(a, i, n-1);
    reverse(a, 0, n-1);

    return a;
}

int main(int argc, char *argv[])
{
    char a[] = "abcdefgh";
    printf("%s ", a);
    printf("trans to %s\n", trans(a, 8, 3));
    printf("trans back to %s\n", trans_2(a, 8, 5));
    printf("again trans to %s\n", trans_3(a, 8, 3));

    return 0;
}
